package com.untrance.shop.web.controller;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Random;

import com.untrance.shop.core.service.*;
import com.untrance.shop.model.*;
import org.apache.commons.io.IOUtils;
import org.mortbay.log.Log;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.servlet.ModelAndView;

import com.google.appengine.api.datastore.Key;
import com.untrance.shop.common.enums.AvailabilityType;
import com.untrance.shop.common.enums.ProductOrderType;
import com.untrance.shop.common.enums.UserRole;
import com.untrance.shop.core.dao.UserDao;

/**
 * @author eugene zadyra
 */
@Controller
public class TestController {

	@Autowired
	ProductService productService;
	@Autowired
	ImageService imageService;
	@Autowired
	CategoryService categoryService;
	@Autowired
	UserService userService;
	@Autowired
	UserDao userDao;
	@Autowired
	CommentService commentService;
	
	

	private Random random = new Random();
	private final int images = 6;
	private ArrayList<Key> imageKeys;
	private final List<Category> categories = new ArrayList<Category>();

	@RequestMapping("/preloadtestdata.html")
	public ModelAndView preloadData() {
		random = new Random();
		testEnums();
		createCategories();
		loadImage();
		loadUsers();
		loadProducts();
		return new ModelAndView("index");
	}

	private void testEnums() {
		for(ProductOrderType type: ProductOrderType.values()){
			Log.info(type.name()+"="+type.getDescription());
		}
	}


	private void loadComments(Key productKey){
		User u = new ArrayList<User>(userDao.findAll()).get(0);
		for(int i=0;i<30;i++){
			Comment c = new Comment();
			c.setMessage("Comment #"+i);
			c.setTimeAdded(new Date());
			c.setUserKey(u.getId());
			c.setProductKey(productKey);
			commentService.addComment(c);
		}
	}

	private void loadUsers() {
		User u1 = new User();
		u1.setBirthDate(new Date());
		u1.setEnabled(true);
		u1.setFirstName("Eugene");
		u1.setLastName("Zadyra");
		u1.setLocked(false);
		u1.setPassword("1234");
		u1.setUsername("ezadyra");
		u1.setUserRole(UserRole.ROLE_CUSTOMER);
		userService.addUser(u1);
		
		User u2 = new User();
		u2.setBirthDate(new Date());
		u2.setEnabled(true);
		u2.setFirstName("Admin");
		u2.setLastName("Admin");
		u2.setLocked(false);
		u2.setPassword("1234");
		u2.setUsername("admin");
		u2.setUserRole(UserRole.ROLE_ADMIN);
		userService.addUser(u2);
	}

	private void loadImage() {
		imageKeys = new ArrayList<Key>();
		for (int i = 0; i < images; i++) {
			String imageName = "/temp/product"+i+".jpg";
			InputStream is = TestController.class.getResourceAsStream(imageName);
			ByteArrayOutputStream baos = new ByteArrayOutputStream();
			try {
				IOUtils.copy(is, baos);
			} catch (IOException e) {
				e.printStackTrace();
			}
			Image image = imageService.saveImage(imageName, baos.toByteArray());
			imageKeys.add(image.getId());
		}
	}

	private void loadProducts() {
		int productsCount = 30;
		for (int i = 0; i < productsCount; i++) {
			Product p = createProduct();
			productService.addProduct(p);
			loadComments(p.getId());
		}
	}

	private Product createProduct() {
		Product p = new Product();
		p.setAvailability(AvailabilityType.AVAILABLE);
		p.setName("Name" + random.nextInt());
		p.setShortDescription(prepareDescription());
		p.setOldPrice(random.nextInt(100)+random.nextFloat());
		p.setNewPrice(random.nextInt(100)+random.nextFloat());
		p.setImageName(imageKeys.get(random.nextInt(5)).getId() + "");
		p.setCategoryKey(categories.get(random.nextInt(categories.size())).getId());
		return p;
	}
	
	
	/**
	 * Prepare short description for testing css.
	 */
	private final String[] descElements = "A classic jean beloved for its comfortable style which fits straight through the seat thigh and leg Its straight-cut waistband hits at the waist and sits evenly front and back".split(" ");
	private String prepareDescription(){
		StringBuilder description = new StringBuilder();
		for(int i=0;i<random.nextInt(10);i++){
			description.append(descElements[random.nextInt(descElements.length)]).append(" ");
		}
		return description.toString();
	}
	
	
	private void createCategories(){
		final List<Category> parentList = createCategoryListOfLevel(null, 0);
		Category c = parentList.get(2);
		for(int i=1;i<4;i++){
			c.setChildren(createCategoryListOfLevel(c.getId(), i));
			c = c.getChildren().get(2);
		}
	}
	
	private List<Category> createCategoryListOfLevel(Key parentKey, int level){
		final List<Category> list = new ArrayList<Category>();
		for(int i=0;i<3;i++){
			final Category c = new Category();
			c.setName("Category"+i+"_Level"+level);
			c.setLevel(level);
			c.setParentCategoryKey(parentKey);
			categoryService.add(c);
			list.add(c);
			categories.add(c);
		}
		return list;
	}

}
